package test;

import static org.junit.Assert.*;


import java.util.ArrayList;

import movement.Location;

import org.junit.*;

import unit.*;

import dispatch.*;
import emergency.Emergency;
import emergency.Fire.Size;
import emergency.Severity;
import emergency.TrafficAccident;


public class testGarage {

	private DispatchCenter center;
	private Garage garage;
	Location locationGarage;
	Ambulance ambu1 , ambu2, ambu3, ambu4;
	
    @SuppressWarnings("unused")
	@Before
    public void setUp() throws Exception { 
    	center = new DispatchCenter("DC 1",new Location(45,45,"DC 1 - Location"),new Location(60,60,"GarageLocation"));
    	locationGarage = new Location(-30,-30,"TestGarage");
    	garage = new Garage(locationGarage, center);
    	
    	ambu1 = new Ambulance("Ambulance-1", 0,garage);
    	ambu2 = new Ambulance("Ambulance-2", 0,garage);
    	ambu3 = new Ambulance("Ambulance-3", 0,garage);
    	ambu4 = new Ambulance("Ambulance-4", 0,garage);
    	PoliceCar police1 = new PoliceCar("Police-1", 0,garage);
    	PoliceCar police2 = new PoliceCar("Police-2", 0,garage);
    	PoliceCar police3 = new PoliceCar("Police-3", 0,garage);
    	PoliceCar police4 = new PoliceCar("Police-4", 0,garage);
    	PoliceCar police5 = new PoliceCar("Police-5", 0,garage);
    	PoliceCar police6 = new PoliceCar("Police-6", 0,garage);
    	FireTruck fire1 = new FireTruck("Firetruck-1",0,garage,Size.FACILITY);
    	FireTruck fire2 = new FireTruck("Firetruck-2",0,garage,Size.HOUSE);
    	FireTruck fire3 = new FireTruck("Firetruck-3",0,garage,Size.FACILITY);
    	FireTruck fire4 = new FireTruck("Firetruck-4",0,garage,Size.LOCAL);
    }
    
    @SuppressWarnings("unused")
	@Test
    public void testAddUnit(){
    	assertEquals(14,garage.getUnitsClone().size());
    	PoliceCar pc = new PoliceCar("NewOne!", 100, garage);
    	assertEquals(15,garage.getUnitsClone().size());
    }
    
    @Test 
    public void testCanHaveAsDispatchCenter(){
    	assertTrue(garage.canHaveAsDispatchCenter(new DispatchCenter("DC 1",new Location(45,45,"DC 1 - Location"),new Location(60,60,"GarageLocation"))));
    	assertFalse(garage.canHaveAsDispatchCenter(null));
    }
    
    @Test 
    public void testCanHaveAsLocation(){
    	assertTrue(garage.canHaveAsLocation(new Location(10,10,"Valid")));
    	assertFalse(garage.canHaveAsLocation(null));
    }
    
    @Test
    public void testConstructor(){
    	Location loc = new Location(20, 20, "location");
    	Garage x = new Garage(loc, center);
    	assertEquals(x.getLocation(),loc);
    	assertEquals(center, x.getDispatchcenter());
    	assertEquals(0,x.getUnitsClone().size());
    	
    	assertEquals(garage.getLocation(),locationGarage);
    	assertEquals(garage.getDispatchcenter(),center);
    	assertEquals(14,garage.getUnitsClone().size());
    	assertNotNull(garage.getHospitalboard());
    }
    
    @SuppressWarnings("unused")
	@Test (expected=IllegalArgumentException.class)
    public void testConstructorInvalid(){
    	Garage x = new Garage(null, center);	
    }
    
	@Test
    public void testCreateCorrectGarage() {
    	//create correct garage
    	garage = new Garage(locationGarage,center);
    	assertEquals(garage.getLocation(),locationGarage);
    	assertEquals(garage.getDispatchcenter(),center);
    }
    
    @SuppressWarnings("unused")
	@Test (expected=IllegalArgumentException.class) 
    public void testCreateNullDispatchCenterGarage() {
    	//create incorrect garage (dispatchcenter = null)
		Garage NoDispatchCenterGarage = new Garage(locationGarage,null);
    }
    
    @Test 
    public void testGetAvailableUnits(){
    	// garage contains 14 units at start
    	assertEquals(garage.getAvailableUnits().size(), 14);
    	ambu1.assignEmergency(new TrafficAccident(new Location(10,10,"a"), Severity.NORMAL, center, 1, 1));
    	// and 13 after assigning one
    	assertEquals(garage.getAvailableUnits().size(), 13);
    	
    }
    
    @Test 
    public void testGetAvailableUnitsFromType(){
    	// garage contains 4 units of each at the start, except 6 policecars
    	assertEquals(garage.getAvailableUnits("Ambulance").size(), 4);
    	assertEquals(garage.getAvailableUnits("FireTruck").size(), 4);
    	assertEquals(garage.getAvailableUnits("PoliceCar").size(), 6);
    	
    	ambu1.assignEmergency(new TrafficAccident(new Location(10,10,"a"), Severity.NORMAL, center, 1, 1));
    	assertEquals(garage.getAvailableUnits("Ambulance").size(), 3);
    }
    
    @Test 
    public void testGettersAndSetters() {
    	assertEquals(garage.getDispatchcenter(), center);
    	assertEquals(garage.getLocation(),locationGarage);
    	assertEquals(garage.getUnitsClone().size(),14);
    	assertEquals(garage.getHospitalboard().getHospitalsClone().size(),0);
    	ArrayList<Unit> testUnits = new ArrayList <Unit>();
    	testUnits.add(ambu1);
    	testUnits.add(ambu2);
    	testUnits.add(ambu3);
    	testUnits.add(ambu4);
    	garage.setUnits(testUnits);
    	assertEquals(garage.getUnitsClone(),testUnits);
    	assertEquals(garage.getUnitsClone().size(),4);
    	DispatchCenter x = new DispatchCenter("DC 1",new Location(45,45,"DC 1 - Location"),new Location(60,60,"GarageLocation"));
    	garage.setDispatchcenter(x);
    	assertEquals(garage.getDispatchcenter(), x);
    }
    
    @Test 
    public void testGetUnitsFromName(){
    	assertEquals(ambu1, garage.getUnit("Ambulance-1"));
    	assertEquals(ambu2, garage.getUnit("Ambulance-2"));
    	assertEquals(ambu3, garage.getUnit("Ambulance-3"));
    	
    }
    
    @Test 
    public void testGetUnitsFromType(){
    	Location l = new Location(10,10,"a");
    	Emergency e = new TrafficAccident(l, Severity.NORMAL, center, 1, 1);
    	
    	assertEquals(garage.getAvailableUnits("Ambulance").size(), 4);
    	assertEquals(garage.getAvailableUnits("PoliceCar").size(), 6);
    	assertEquals(garage.getAvailableUnits("FireTruck").size(), 4);
    	ambu1.assignEmergency(e);
    	//still in the garage, we didn't ask for available units... 
    	assertEquals(garage.getAvailableUnits("Ambulance").size(), 3);
    	assertTrue(ambu1.isAssigned());
    	
    }
    
    @Test
    public void testNameAlreadyOccurs(){
    	assertTrue(garage.nameAlreadyOccurs("Ambulance-2"));
    	assertTrue(garage.nameAlreadyOccurs("Police-6"));
    	assertFalse(garage.nameAlreadyOccurs("jaja"));
    	assertFalse(garage.nameAlreadyOccurs("Policecar"));
    }

}
